Django 电子商务平台开发教程
1. Django 简介和特性
Django 是一个高级 Python Web 框架,鼓励快速开发和简洁、实用的设计。它遵循 MVT(Model-View-Template)架构,提供了许多内置功能,如用户认证、内容管理、表单处理、文件上传等。
1.1 Django 的主要特性
- ORM(对象关系映射):简化数据库操作。
- Admin 后台:自动生成管理界面。
- 表单处理:简化表单创建和验证。
- 安全特性:内置 CSRF 保护、XSS 防御等。
2. 安装和环境设置
2.1 安装 Django
pip install django
2.2 创建项目
django-admin startproject ecommerce_platform
2.3 运行开发服务器
cd ecommerce_platform
python manage.py runserver
3. 项目结构和管理命令
3.1 项目结构
ecommerce_platform/
manage.py
ecommerce_platform/
__init__.py
settings.py
urls.py
asgi.py
wsgi.py
3.2 常用管理命令
- 创建应用:
python manage.py startapp products - 运行服务器:
python manage.py runserver - 创建数据库迁移:
python manage.py makemigrations - 应用数据库迁移:
python manage.py migrate
4. MVT 架构
4.1 Model
模型是数据的唯一且明确的信息源。它包含数据的基本字段和行为。
4.2 View
视图是处理请求并返回响应的逻辑。它可以是函数或类。
4.3 Template
模板是用于生成 HTML 的文本文件。它包含变量和标签。
5. 第一个 Django 应用
5.1 创建应用
python manage.py startapp products
5.2 定义模型
# products/models.py
from django.db import models
class Product(models.Model):
name = models.CharField(max_length=255)
price = models.DecimalField(max_digits=10, decimal_places=2)
description = models.TextField()
5.3 创建和应用迁移
python manage.py makemigrations
python manage.py migrate
6. 模型定义和字段类型
6.1 常用字段类型
CharField:用于短字符串。TextField:用于长文本。IntegerField:用于整数。DecimalField:用于浮点数。DateTimeField:用于日期和时间。
6.2 自定义模型方法
class Product(models.Model):
# ...
def is_expensive(self):
return self.price > 1000
7. 数据库迁移
7.1 创建迁移
python manage.py makemigrations
7.2 应用迁移
python manage.py migrate
8. 查询集和管理器
8.1 查询集
查询集是数据库查询的集合。
products = Product.objects.all()
expensive_products = Product.objects.filter(price__gt=1000)
8.2 管理器
管理器是用于创建查询集的对象。
class ProductManager(models.Manager):
def expensive_products(self):
return self.filter(price__gt=1000)
class Product(models.Model):
# ...
objects = ProductManager()
9. 模型关系
9.1 一对多关系
class Category(models.Model):
name = models.CharField(max_length=255)
class Product(models.Model):
category = models.ForeignKey(Category, on_delete=models.CASCADE)
# ...
9.2 多对多关系
class Tag(models.Model):
name = models.CharField(max_length=255)
class Product(models.Model):
tags = models.ManyToManyField(Tag)
# ...
10. 自定义模型方法
class Product(models.Model):
# ...
def is_expensive(self):
return self.price > 1000
11. 函数视图和类视图
11.1 函数视图
# products/views.py
from django.http import HttpResponse
def product_list(request):
return HttpResponse("Product List")
11.2 类视图
from django.views import View
class ProductListView(View):
def get(self, request):
return HttpResponse("Product List")
12. URL 模式和命名
12.1 URL 模式
# products/urls.py
from django.urls import path
from . import views
urlpatterns = [
path('products/', views.product_list, name='product_list'),
]
12.2 命名 URL
<a href="{% url 'product_list' %}">Product List</a>
13. 视图参数和请求处理
13.1 视图参数
def product_detail(request, product_id):
return HttpResponse(f"Product {product_id}")
13.2 请求处理
def product_detail(request, product_id):
if request.method == 'GET':
return HttpResponse(f"Product {product_id}")
elif request.method == 'POST':
# Handle POST request
pass
14. 通用视图
14.1 列表视图
from django.views.generic import ListView
from .models import Product
class ProductListView(ListView):
model = Product
template_name = 'products/product_list.html'
14.2 详情视图
from django.views.generic import DetailView
from .models import Product
class ProductDetailView(DetailView):
model = Product
template_name = 'products/product_detail.html'
15. 中间件
15.1 自定义中间件
# middleware.py
class SimpleMiddleware:
def __init__(self, get_response):
self.get_response = get_response
def __call__(self, request):
# Code to be executed for each request before
# the view (and later middleware) are called.
response = self.get_response(request)
# Code to be executed for each request/response after
# the view is called.
return response
16. 模板语法和标签
16.1 模板语法
<h1>{{ product.name }}</h1>
<p>{{ product.description }}</p>
16.2 模板标签
{% if product.is_expensive %}
<p>Expensive</p>
{% else %}
<p>Affordable</p>
{% endif %}
17. 模板继承
17.1 基础模板
<!-- base.html -->
<html>
<head>
<title>{% block title %}My Site{% endblock %}</title>
</head>
<body>
<div id="content">
{% block content %}{% endblock %}
</div>
</body>
</html>
17.2 继承模板
<!-- product_list.html -->
{% extends "base.html" %}
{% block title %}Product List{% endblock %}
{% block content %}
<h1>Product List</h1>
<ul>
{% for product in products %}
<li>{{ product.name }}</li>
{% endfor %}
</ul>
{% endblock %}
18. 上下文处理器
18.1 自定义上下文处理器
# context_processors.py
def cart_items(request):
return {'cart_items': request.session.get('cart', [])}
18.2 注册上下文处理器
# settings.py
TEMPLATES = [
{
# ...
'OPTIONS': {
'context_processors': [
# ...
'ecommerce_platform.context_processors.cart_items',
],
},
},
]
19. 自定义模板标签和过滤器
19.1 自定义过滤器
# templatetags/custom_filters.py
from django import template
register = template.Library()
@register.filter
def currency(value):
return f"${value:.2f}"
19.2 使用过滤器
{{ product.price|currency }}
20. 静态文件处理
20.1 配置静态文件
# settings.py
STATIC_URL = '/static/'
STATICFILES_DIRS = [
BASE_DIR / "static",
]
20.2 使用静态文件
{% load static %}
<link rel="stylesheet" href="{% static 'css/styles.css' %}">
21. Django Form 类
21.1 创建表单
# forms.py
from django import forms
class ProductForm(forms.Form):
name = forms.CharField(max_length=255)
price = forms.DecimalField(max_digits=10, decimal_places=2)
description = forms.CharField(widget=forms.Textarea)
21.2 使用表单
# views.py
from django.shortcuts import render
from .forms import ProductForm
def add_product(request):
if request.method == 'POST':
form = ProductForm(request.POST)
if form.is_valid():
# Process form data
pass
else:
form = ProductForm()
return render(request, 'products/add_product.html', {'form': form})
22. 表单验证
22.1 自定义验证
class ProductForm(forms.Form):
# ...
def clean_price(self):
price = self.cleaned_data['price']
if price < 0:
raise forms.ValidationError("Price cannot be negative")
return price
23. ModelForm
23.1 创建 ModelForm
# forms.py
from django.forms import ModelForm
from .models import Product
class ProductForm(ModelForm):
class Meta:
model = Product
fields = ['name', 'price', 'description']
23.2 使用 ModelForm
# views.py
from django.shortcuts import render, redirect
from .forms import ProductForm
def add_product(request):
if request.method == 'POST':
form = ProductForm(request.POST)
if form.is_valid():
form.save()
return redirect('product_list')
else:
form = ProductForm()
return render(request, 'products/add_product.html', {'form': form})
24. 表单集 (Formsets)
24.1 创建表单集
# forms.py
from django.forms import modelformset_factory
from .models import Product
ProductFormSet = modelformset_factory(Product, fields=('name', 'price'), extra=2)
24.2 使用表单集
# views.py
from django.shortcuts import render
from .forms import ProductFormSet
def manage_products(request):
formset = ProductFormSet(request.POST or None)
if request.method == 'POST' and formset.is_valid():
formset.save()
return render(request, 'products/manage_products.html', {'formset': formset})
25. 文件上传处理
25.1 配置文件上传
# settings.py
MEDIA_URL = '/media/'
MEDIA_ROOT = BASE_DIR / "media"
25.2 处理文件上传
# models.py
class Product(models.Model):
# ...
image = models.ImageField(upload_to='products/')
26. 用户认证系统
26.1 用户注册
# views.py
from django.contrib.auth.forms import UserCreationForm
from django.shortcuts import render, redirect
def register(request):
if request.method == 'POST':
form = UserCreationForm(request.POST)
if form.is_valid():
form.save()
return redirect('login')
else:
form = UserCreationForm()
return render(request, 'registration/register.html', {'form': form})
26.2 用户登录
# views.py
from django.contrib.auth import authenticate, login
from django.shortcuts import render, redirect
def user_login(request):
if request.method == 'POST':
username = request.POST['username']
password = request.POST['password']
user = authenticate(request, username=username, password=password)
if user is not None:
login(request, user)
return redirect('home')
return render(request, 'registration/login.html')
27. 自定义用户模型
27.1 创建自定义用户模型
# models.py
from django.contrib.auth.models import AbstractUser
class CustomUser(AbstractUser):
# Add custom fields
pass
27.2 配置自定义用户模型
# settings.py
AUTH_USER_MODEL = 'accounts.CustomUser'
28. 权限和组
28.1 创建权限
from django.contrib.auth.models import Permission
from django.contrib.contenttypes.models import ContentType
from .models import Product
content_type = ContentType.objects.get_for_model(Product)
permission = Permission.objects.create(
codename='can_publish',
name='Can Publish Products',
content_type=content_type,
)
28.2 分配权限
from django.contrib.auth.models import Group
group = Group.objects.create(name='Publishers')
group.permissions.add(permission)
29. 登录、注销和注册视图
29.1 登录视图
from django.contrib.auth.views import LoginView
urlpatterns = [
path('login/', LoginView.as_view(), name='login'),
]
29.2 注销视图
from django.contrib.auth.views import LogoutView
urlpatterns = [
path('logout/', LogoutView.as_view(), name='logout'),
]
29.3 注册视图
from django.contrib.auth.forms import UserCreationForm
from django.views.generic.edit import CreateView
class RegisterView(CreateView):
form_class = UserCreationForm
template_name = 'registration/register.html'
success_url = '/login/'
30. 基于类的权限控制
30.1 权限检查
from django.contrib.auth.mixins import LoginRequiredMixin
from django.views.generic import View
class ProtectedView(LoginRequiredMixin, View):
def get(self, request):
return HttpResponse("Protected View")
31. Admin 站点定制
31.1 模型注册
# admin.py
from django.contrib import admin
from .models import Product
admin.site.register(Product)